package com.welkom.everydate.security.implementations;

import java.util.Collection;
import java.util.HashMap;

import java.util.ArrayList;  
import java.util.Collection;  
import java.util.HashMap;  
import java.util.Iterator;  
import java.util.List;  
  
import javax.annotation.PostConstruct;  
import javax.annotation.Resource;  
 
import org.springframework.security.access.ConfigAttribute;  
import org.springframework.security.access.SecurityConfig;  
import org.springframework.security.web.FilterInvocation;  
import org.springframework.util.AntPathMatcher;

import com.welkom.everydate.dao.RoleDao;
import com.welkom.everydate.domain.Authority;
import com.welkom.everydate.domain.Role;
import com.welkom.everydate.security.interfaces.CustomFilterInvocationSecurityMetadataSource;
import com.welkom.everydate.services.interfaces.AuthorityService;
import com.welkom.everydate.services.interfaces.ResourceService;
import org.springframework.stereotype.Service;  
@Service("customInvocationSecurityMetadataSource")  
public class CustomInvocationSecurityMetadataSourceImpl implements CustomFilterInvocationSecurityMetadataSource  {
	
	
	@Resource  
    private ResourceService resourceService;  
      
    @Resource  
    private AuthorityService authorityService;  
    @Resource
    private RoleDao roleDao;
  
    private AntPathMatcher urlMatcher = new AntPathMatcher();  
    private HashMap<String, Collection<ConfigAttribute>> resourceMap = null;  
    
    @PostConstruct  
    public void init() {  
        loadResourceDefine();  
    }  
    
    /** 
     *  
     *
     */  
    private void loadResourceDefine() {  
  
        
    	List<Role> roles=roleDao.getAllRoles();  
        resourceMap = new HashMap<String, Collection<ConfigAttribute>>();  
  
        for (Role role : roles) {  
            String roleName =role.getRoleName();  
            ConfigAttribute ca = new SecurityConfig(role.getRoleName());  
            List<com.welkom.everydate.domain.Resource> resources=new ArrayList<com.welkom.everydate.domain.Resource>();
            List<Authority> authorities=role.getAuthorities();
            for(Authority authority:authorities){
            	resources.addAll(authority.getResources());
            }
            for (com.welkom.everydate.domain.Resource resource : resources) {   
                String url = resource.getResourceString();  
                if (resourceMap.containsKey(url)) {  
  
                    Collection<ConfigAttribute> value = resourceMap.get(url);  
                    value.add(ca);  
                    resourceMap.put(url, value);  
                } else {  
                    Collection<ConfigAttribute> atts = new ArrayList<ConfigAttribute>();  
                    atts.add(ca);  
                    resourceMap.put(url, atts);  
                }  
  
            }  
  
        }  
  
    }  
    
  
    private Collection<ConfigAttribute> listToCollection(List<Role> roles) {  
        List<ConfigAttribute> list = new ArrayList<ConfigAttribute>();  
  
        for (Role role : roles) {  
            list.add(new SecurityConfig(role.getRoleName()));  
  
        }  
        return list;  
    }  
    
	public Collection<ConfigAttribute> getAttributes(Object object)
			throws IllegalArgumentException {
		// TODO Auto-generated method stub
		
       String url = ((FilterInvocation)object).getRequestUrl();  
       if("/".equals(url)){  
           return null;  
       }  
        int firstQuestionMarkIndex = url.indexOf(".");  
       
        if(firstQuestionMarkIndex != -1){  
            url = url.substring(0,firstQuestionMarkIndex);  
        }  
          
        Iterator<String> ite = resourceMap.keySet().iterator();  
       
        while (ite.hasNext()) {  
            String resURL = ite.next();  
            if(urlMatcher.match(resURL,url)){  
                return resourceMap.get(resURL);  
            }  
        }  
        return null;  
	}

	public Collection<ConfigAttribute> getAllConfigAttributes() {
		// TODO Auto-generated method stub
		return null;
	}

	public boolean supports(Class<?> clazz) {
		// TODO Auto-generated method stub
		return true;
	}

}
